package com.bkhc.product.service;

import com.alibaba.druid.support.json.JSONUtils;
import com.alibaba.fastjson.JSONObject;
import com.bkhc.common.entity.Lookup;
import com.bkhc.common.entity.User;
import com.bkhc.common.enu.BrandStatusEnum;
import com.bkhc.common.repository.LookupRepository;
import com.bkhc.common.repository.UserRepository;
import com.bkhc.common.service.UserService;
import com.bkhc.common.util.CommonUtil;
import com.bkhc.common.util.response.PageUtil;
import com.bkhc.common.util.response.ResultCode;
import com.bkhc.common.util.response.ResultJson;
import com.bkhc.common.vo.UserBean;
import com.bkhc.product.entity.*;
import com.bkhc.product.repository.*;
import com.bkhc.product.vo.GoodsVO;
import com.bkhc.product.vo.SaveBrandGoodsVO;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Sort;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;

import java.math.BigDecimal;
import java.util.*;
import java.util.stream.Collectors;

@Service
public class BrandService {

    @Autowired
    private BrandRepository repository;
    @Autowired
    private BrandGoodsRepository brandGoodsrepository;
    @Autowired
    private BrandProductRepository brandProductRepository;
    @Autowired
    private GoodsRepository goodsRepository;
    @Autowired
    private ProductRepository productRepository;
    @Autowired
    private LookupRepository lookupRepository;
    @Autowired
    private PriceRuleRepository priceRuleRepository;
    @Autowired
    private BrandGoodPriceRepository brandGoodPriceRepository;
    @Autowired
    private GoodspecRepository goodspecRepository;

    @Autowired
    private ProductPriceRepository productPriceRepository;

   @Autowired
    private PriceService priceService;
    @Autowired
    private BuessinesRepository buessinesRepository;
    @Autowired
    private UserRepository userRepository;

    public ResultJson<?> findBrand(Brand brand, int pageIndex, int pageSize){
        Sort.Order orders = new Sort.Order(Sort.Direction.DESC, "updateDate");
        PageRequest pageRequest = PageRequest.of(pageIndex-1, pageSize, Sort.by(orders));
        Page<Brand> page = null;
        if(brand == null){
            page = repository.findAll(pageRequest);
        }else {
            page = repository.findAll(brand, pageRequest);
        }
        PageUtil pageUtil = new PageUtil(page);
        ResultJson<PageUtil> resultJson = ResultJson.success();
        resultJson.setData(pageUtil);
        return  resultJson;
    }

    public ResultJson<?> updateBrand(Brand brand) {
        Brand o = repository.findByBrandCode(brand.getBrandCode());
        if(o!=null){
            ResultJson<Page<Product>> resultJson = ResultJson.failure(ResultCode.ISEXIT_RESURCE);
            return resultJson;
        }
        repository.save(brand);
        return ResultJson.success();
    }


    public ResultJson<?> deleteBrand(String brandCode) {
        repository.deleteByBrandCode(brandCode);
        return ResultJson.success();
    }

    public ResultJson<?> addBrand(Brand brand) {
        Brand b=repository.findByBrandName(brand.getBrandName());
        if(b!=null){
            ResultJson<Brand> resultJson = ResultJson.failure(ResultCode.ISEXIT_RESURCE);
            return resultJson;
        }
        brand.setStatus(BrandStatusEnum.NotSettled);
        UserBean u = CommonUtil.getCrruentUser();
        brand.setCreator(u.getUserId());
        brand.setUpdator(u.getUserId());
        repository.save(brand);
        return ResultJson.success();
    }

    public ResultJson<?> getBrandGoodsByProductAndBrand(String productCode,String brandCode) {
        List<BrandGoods> brandGoods = brandGoodsrepository.findByProductCodeAndBrandCode(productCode,brandCode);
        if(!CollectionUtils.isEmpty(brandGoods)){
            for(BrandGoods bg:brandGoods){
                List<GoodsSpec> goodspec = goodspecRepository.findByGoodsCode(bg.getGoodsCode());
                bg.setGoodsSpecList(goodspec);
            }
        }
        ResultJson<List<BrandGoods>> resultJson = ResultJson.success();
        resultJson.setData(brandGoods);
        return resultJson;
    }


    /**
     * 查询商品价格
     * @param
     * @param
     * @return
     */
//    public ResultJson<?> getBrandGoodsByProductAndBrand(String productCode,String brandCode) {
//        List<BrandGoods> brandGoods = brandGoodsrepository.findByProductCodeAndBrandCode(productCode,brandCode);
//        for (BrandGoods bg1:brandGoods) {
//            //将brandGoods里面的list<BrandGoodPrice>拿出来
//            List<BrandGoodPrice> price = bg1.getPrices();
//            //获取list<BrandGoodPrice>里面的价格
//            //循环输出单个price
//            for (BrandGoodPrice p : price) {
//                if (p.getPrice().equals(BigDecimal.ZERO)) {
//                    break;
//                } else {
//                    if (!CollectionUtils.isEmpty(brandGoods)) {
//                        for (BrandGoods bg : brandGoods) {
//                            List<GoodsSpec> goodspec = goodspecRepository.findByGoodsCode(bg.getGoodsCode());
//                            bg.setGoodsSpecList(goodspec);
//                        }
//                    }
//                }
//            }
//
//        }
//
//        ResultJson<List<BrandGoods>> resultJson = ResultJson.success();
//        resultJson.setData(brandGoods);
//        return resultJson;
//    }



    public ResultJson<?> brandAddProductCheckbox(String productCode, String brandCode) {
        List<GoodsVO> gvo = new ArrayList<GoodsVO>();
        List<Goods> goodsList = goodsRepository.findByProductCode(productCode);
        if(CollectionUtils.isEmpty(goodsList)){
            ResultJson.failure(ResultCode.NOT_FOUND);
        }

        for(Goods goods:goodsList){
            GoodsVO vo = new GoodsVO();
            vo.setGoodsCode(goods.getGoodsCode());
            List<GoodsSpec> goodsSpecs = goodspecRepository.findByGoodsCode(goods.getGoodsCode());
            if(!CollectionUtils.isEmpty(goodsSpecs)){
                String sb = null;
                for(GoodsSpec gs :goodsSpecs){
                    if(sb==null){
                        sb = gs.getSpecName()+gs.getSpecValue();
                        continue;
                    }
                        sb = sb+"/"+gs.getSpecName()+gs.getSpecValue();
                }
                vo.setSpecDescription(sb);
                BrandGoods bg= brandGoodsrepository.findByGoodsCodeAndBrandCode(goods.getGoodsCode(),brandCode);
                if(bg==null){
                    vo.setCheck("0");
                }else{
                    vo.setCheck("1");
                }
                gvo.add(vo);
            }
        }
        ResultJson<List<GoodsVO>> resultJson = ResultJson.success();
        resultJson.setData(gvo);
        return resultJson;
    }

    public ResultJson<?> updateBrandGoods(SaveBrandGoodsVO vo) {
        BrandProduct brandProduct = brandProductRepository.findByProductCodeAndBrandCode(vo.getProductCode(), vo.getBrandCode());
        List<String> goodsCodes = vo.getGoodsCodeList();
        UserBean u = CommonUtil.getCrruentUser();
        Product product=productRepository.findByProductCode(vo.getProductCode());
        Brand brand = repository.findByBrandCode(vo.getBrandCode());
        if(brandProduct==null&&!CollectionUtils.isEmpty(goodsCodes)){
            BrandProduct bp = new BrandProduct();
            bp.setProductName(product.getProductName());
            bp.setBrandCode(vo.getBrandCode());
            bp.setProductCode(product.getProductCode());
            bp.setBrandName(brand.getBrandName());
            brandProductRepository.save(bp);
            if(!CollectionUtils.isEmpty(goodsCodes)){
                List<BrandGoods> bgs = new ArrayList<BrandGoods>();
                for(String goodsCode:goodsCodes){
                    BrandGoods bg = new BrandGoods();
                    bg.setBrandCode(vo.getBrandCode());
                    bg.setProductCode(vo.getProductCode());
                    bg.setGoodsCode(goodsCode);
                    bg.setCreator(u.getCreator());
                    bg.setUpdator(u.getCreator());
                    bgs.add(bg);
                }
                brandGoodsrepository.saveAll(bgs);
            }
        }
        if(brandProduct!=null&&CollectionUtils.isEmpty(goodsCodes)){
            brandProductRepository.delete(brandProduct);
            brandGoodsrepository.deleteByBrandCodeAndProductCode(vo.getBrandCode(),vo.getProductCode());
        }
        if(brandProduct!=null&&!CollectionUtils.isEmpty(goodsCodes)){
            List<BrandGoods> bgs = new ArrayList<BrandGoods>();
            brandGoodsrepository.deleteByBrandCodeAndProductCode(vo.getBrandCode(),vo.getProductCode());

            if(!CollectionUtils.isEmpty(goodsCodes)){
                for(String goodsCode:goodsCodes){
                    BrandGoods bg = new BrandGoods();
                    bg.setBrandCode(vo.getBrandCode());
                    bg.setProductCode(vo.getProductCode());
                    bg.setGoodsCode(goodsCode);
                    bg.setCreator(u.getCreator());
                    bg.setUpdator(u.getCreator());
                    bgs.add(bg);
                }
                brandGoodsrepository.saveAll(bgs);
            }
        }


        return ResultJson.success();
    }

    public ResultJson<?> getUnassignedBrand() {
        List<Brand> brands = repository.findUnassigned();
        ResultJson<List<Brand>> resultJson = ResultJson.success();
        resultJson.setData(brands);
        return resultJson;
    }

    public ResultJson<?> saveOrUpdateBrandProductPriceRule(List<PriceRule> priceRules) {
        List<Lookup> lookups = lookupRepository.findByItemClass("Indentity_class");
        if(CollectionUtils.isEmpty(priceRules)||lookups.size()!=priceRules.size()){
            ResultJson<Brand> resultJson = ResultJson.failure(ResultCode.BAD_REQUEST);
            return resultJson;
        }
            priceRuleRepository.saveAll(priceRules);
        ResultJson<?> resultJson = ResultJson.success();
        return  resultJson;
    }

    public ResultJson<?> queryBrandProductPriceRule(String productCode, String brandCode) {
        List<PriceRule> rules = priceRuleRepository.findByProductCodeAndBrandCode(productCode,brandCode);
        ResultJson<List<PriceRule>> resultJson = ResultJson.success();
        resultJson.setData(rules);
        return resultJson;
    }

    public BrandGoodPrice queryBrandProductGoodsPrice(String brandCode,String goodCode) {
        UserBean user = CommonUtil.getCrruentUser();
        String indentity = "";
        if(user == null){
            List<Lookup> indentityList = lookupRepository.findByItemClass("Indentity");
            Lookup defaultIndentity = indentityList.stream().filter(x -> "default".equals(x.getAttr1())).findFirst().get();
            indentity = defaultIndentity.getItemCode();
        }else {
            Map customerMap = buessinesRepository.getCustomerIndentity(user.getUserId());
            indentity=(String) customerMap.get("indentity");
        }
        BrandGoodPrice bgp = brandGoodPriceRepository.findByBrandCodeAndGoodsCodeAndIndentity(brandCode, goodCode, indentity);
        return bgp;
    }

    public ResultJson<?> getUploadPriceRule(String productCode, String brandCode) {
        List<PriceRule> rule = priceRuleRepository.findByProductCodeAndBrandCode(productCode, brandCode);
        List<PriceRule> pricerules = rule.stream().filter(x -> "1".equals(x.getRelateWay())).collect(Collectors.toList());
        if(!CollectionUtils.isEmpty(pricerules)){
            List<Lookup> items = lookupRepository.findByItemClass("Indentity");
            for(PriceRule priceRule:pricerules){
                Lookup lookupItem = items.stream().filter(x -> x.getItemCode().equals(priceRule.getIndentity())).collect(Collectors.toList()).get(0);
                priceRule.setIndentityName(lookupItem.getItemName());
            }
        }
        ResultJson<List<PriceRule>> resultJson = ResultJson.success();
        resultJson.setData(pricerules);
        return resultJson;
    }

    public ResultJson<?> queryUploadPrice(String productCode, String brandCode) {
        List<BrandGoods> goods = brandGoodsrepository.findByProductCodeAndBrandCode(productCode, brandCode);
        if(!CollectionUtils.isEmpty(goods)){
            List<PriceRule> rule = priceRuleRepository.findByProductCodeAndBrandCode(productCode, brandCode);
            for(BrandGoods bg:goods){
                String updateUserId = null;
                Date updateTime = null;
                List<GoodsSpec> goodsSpecs = goodspecRepository.findByGoodsCode(bg.getGoodsCode());
                bg.setGoodsSpecList(goodsSpecs);
                List<BrandGoodPrice> pprices = brandGoodPriceRepository.findByBrandCodeAndGoodsCodeAndStatus(brandCode,bg.getGoodsCode(),"1");
                List<PriceRule> pricerules = rule.stream().filter(x -> "1".equals(x.getRelateWay())).collect(Collectors.toList());
                List<BrandGoodPrice> tem = new ArrayList<>();
                for(PriceRule pr:pricerules){
                    BrandGoodPrice p = pprices.stream().filter(x -> x.getIndentity().equals(pr.getIndentity())).collect(Collectors.toList()).get(0);
                    updateUserId = p.getUpdator();
                    updateTime = p.getUpdateDate();
                    tem.add(p);
                }
                bg.setPrices(tem);
                User u = userRepository.findByUserId(updateUserId);
                if(u != null ){
                    bg.setUpdator(u.getNickname());
                }
                bg.setUpdateDate(updateTime);
            }
        }
        ResultJson<List<BrandGoods>> resultJson = ResultJson.success();
        resultJson.setData(goods);
        return resultJson;

    }

    //合伙人上传规则
    public List<BrandGoods> queryProductorUploadPrice(String productCode, String brandCode) {
        List<BrandGoods> goods = brandGoodsrepository.findByProductCodeAndBrandCode(productCode, brandCode);
        if(!CollectionUtils.isEmpty(goods)){
            List<PriceRule> rule = priceRuleRepository.findByProductCodeAndBrandCode(productCode, brandCode);
            for(BrandGoods bg:goods){
                List<GoodsSpec> goodsSpecs = goodspecRepository.findByGoodsCode(bg.getGoodsCode());
                bg.setGoodsSpecList(goodsSpecs);
                List<BrandGoodPrice> pprices = brandGoodPriceRepository.findByBrandCodeAndGoodsCodeAndStatus(brandCode,bg.getGoodsCode(),"1");
                List<PriceRule> pricerules = rule.stream().filter(x -> "0".equals(x.getRelateWay())).collect(Collectors.toList());
                List<BrandGoodPrice> tem = new ArrayList<>();
                for(PriceRule pr:pricerules){
                    BrandGoodPrice p = pprices.stream().filter(x -> x.getIndentity().equals(pr.getIndentity())).collect(Collectors.toList()).get(0);
                    tem.add(p);
                }
                bg.setPrices(tem);
            }

        }

        return goods;

    }

    public ResultJson<?> getBrandByBrandCode(String brandCode) {
        Brand brand = repository.findByBrandCode(brandCode);
        ResultJson<Brand> resultJson = ResultJson.success();
        resultJson.setData(brand);
        return resultJson;
    }

    public Brand getBrandIntanceByBrandCode(String brandCode) {
        Brand brand = repository.findByBrandCode(brandCode);
        return brand;
    }

    public ResultJson<?> uploadPrice(List<BrandGoodPrice> brandGoodPrices) {
        List<BrandGoodPrice> old = brandGoodPriceRepository.findByProductCodeAndBrandCodeAndStatus(brandGoodPrices.get(0).getProductCode(), brandGoodPrices.get(0).getBrandCode(),"1");
        if(!CollectionUtils.isEmpty(old)){
            for(BrandGoodPrice bgp:old){
                bgp.setStatus("0");
            }
            brandGoodPriceRepository.saveAll(old);
        }
        brandGoodPriceRepository.saveAll(brandGoodPrices);
        BrandProduct bp = new BrandProduct();
        bp.setProductCode(brandGoodPrices.get(0).getProductCode());
        bp.setBrandCode(brandGoodPrices.get(0).getBrandCode());
        priceService.calculatePrice(bp);
        ResultJson<?> resultJson = ResultJson.success();
        return resultJson;
    }

    public List<String> getHead(Product product,String brandCode) {
        List<PriceRule> rule = priceRuleRepository.findByProductCodeAndBrandCode(product.getProductCode(), brandCode);
        //产品合伙人必须有固定价格设置
        List<PriceRule> pricerules = rule.stream().filter(x -> "3".equals(x.getRelateWay())).collect(Collectors.toList());
        if(CollectionUtils.isEmpty(pricerules)){
            return null;
        }
        List<String> head = new ArrayList<>();
        head.add("品牌");
        head.add("产品");
        List<Spec> speclist = product.getProductSpecList();
        for(Spec productSpec:speclist){
            head.add(productSpec.getSpecName());
        }
        for(PriceRule price:pricerules){
            head.add(price.getIndentityName());
        }
        return head;
    }

    public void parsePrice(List<List<String>> result, String brandCode, String productCode) {
        Map<String,BigDecimal> response = new HashMap<>();
        List<String> head = null;
        List<List<String>> data = new ArrayList<>();
        for(int i=0;i<result.size();i++){
            if(i==0){
                head = result.get(i);
            }else{
                data.add(result.get(i));
            }
        }
        List<Map<String,String>> priceMap = new ArrayList<>();
        for(List<String> price:data){
            Map<String,String> map = new HashMap<>();
            for(int index=0;index<price.size();index++){
                if(index<head.size()){
                    if(price.get(index)==null){
                        map.put(head.get(index).toString(),"");
                    }else{
                        map.put(head.get(index).toString(),price.get(index).toString());
                    }

                }

            }
            priceMap.add(map);
        }

        List<PriceRule> rule = priceRuleRepository.findByProductCodeAndBrandCode(productCode, brandCode);
        //产品合伙人必须有固定价格设置
        List<PriceRule> priceRule = rule.stream().filter(x -> "3".equals(x.getRelateWay())).collect(Collectors.toList());

        UserBean u = CommonUtil.getCrruentUser();
        List<BrandGoods> goodslist = (List<BrandGoods>)(getBrandGoodsByProductAndBrand(productCode,brandCode).getData());

        //重新初始化固定值价格规则、未上传得价格默认为0
        Map<String,BigDecimal> goodsFixpriceMap = new HashMap();
        for(BrandGoods goods:goodslist){
            goodsFixpriceMap.put(goods.getGoodsCode(),new BigDecimal(0));
        }
        for (PriceRule ruletem : priceRule) {
            ruletem.setFixPrice(JSONUtils.toJSONString(goodsFixpriceMap));
        }
        for(Map<String,String> price:priceMap){
            for(BrandGoods goods:goodslist){
                boolean flag = true;
                List<GoodsSpec> goodspecs = goods.getGoodsSpecList();
                for(GoodsSpec spec:goodspecs){
                    if(!price.get(spec.getSpecName()).equals(spec.getSpecValue())){
                        flag = false;
                        break;
                    }
                }
                if(flag == true) {
                    for (PriceRule ruletem : priceRule) {
                        if(price.containsKey(ruletem.getIndentityName())){
                            String fixprice = ruletem.getFixPrice();
                            JSONObject json = JSONObject.parseObject(fixprice);
                            if(StringUtils.isEmpty(price.get(ruletem.getIndentityName()))){
                                json.put(goods.getGoodsCode(),"0");
                            }else{
                                json.put(goods.getGoodsCode(),price.get(ruletem.getIndentityName()));
                            }
                            ruletem.setFixPrice(json.toJSONString());
                        }
                    }
                }
            }
        }
        priceRuleRepository.saveAll(priceRule);
        BrandProduct bp = new BrandProduct();
        bp.setProductCode(productCode);
        bp.setBrandCode(brandCode);
        priceService.calculatePrice(bp);
    }


    public List<GoodsSpec> getGoodsCodeListByList(List<String> goodsCodeList) {
        return  goodspecRepository.findByGoodsCodeIn(goodsCodeList);
    }



}
